<template>
    <a-form :model="form" ref="formRef" :rules="formRules" :label-col="{ span: 6 }" :wrapper-col="{ span: 14 }">
        <a-form-item :label="$t('upperComputer.dataDictionary.parentCode')" name="parentCode">
            <a-tree-select allow-clear treeNodeFilterProp="title" show-search v-model:value="form.parentCode"
                :tree-data="treeData" :field-names="{
                    children: 'childrens',
                    label: 'displayName',
                    key: 'id',
                    value: 'code',
                }" />
        </a-form-item>
        <a-form-item :label="$t('upperComputer.dataDictionary.code')" name="code">
            <a-input v-model:value="form.code" :maxlength="50" :disabled="form.id ? true : false" />
        </a-form-item>
        <a-form-item :label="$t('upperComputer.dataDictionary.displayName')" name="displayName">
            <a-input v-model:value="form.displayName" :maxlength="50" />
        </a-form-item>
        <a-form-item :label="$t('upperComputer.dataDictionary.sort')" name="sort">
            <a-input-number v-model:value="form.sort" :min="1" :precision="0" style="width: 100%" />
        </a-form-item>
        <a-form-item :label="$t('upperComputer.dataDictionary.value')" name="description">
            <a-textarea v-model:value="form.value" autoSize :maxlength="50" showCount />
        </a-form-item>
    </a-form>
</template>

<script setup lang='ts'>
import i18n from '@/i18n';
import { DataDictionaryDto } from '@/models/data-dictionary';
import { getDataDictionaryApi, getDataDictionariesApi, postDataDictionaryApi, putDataDictionaryApi } from '@/services/data-dictionary';
import { message, type FormInstance } from 'ant-design-vue';
import type { Rule } from 'ant-design-vue/lib/form';
import { onMounted, ref, type Ref } from 'vue';
import type { TreeSelectProps } from 'ant-design-vue/lib/vc-tree-select/TreeSelect';
import type { BaseOptionType } from 'ant-design-vue/lib/select';

const props = defineProps<{ id: number, code: string }>();
defineExpose({ ok });

const treeData: Ref<BaseOptionType | undefined> = ref<TreeSelectProps['treeData']>();
const form: Ref<DataDictionaryDto> = ref<DataDictionaryDto>(new DataDictionaryDto);
const formRef: Ref<FormInstance | undefined> = ref<FormInstance>();
const formRules: Record<string, Rule[]> = {
    code: [
        { required: true, trigger: 'blur', validator: codeValidator },
    ],
    displayName: [
        {
            required: true,
            max: 50,
            message: i18n.global.t('upperComputer.dataDictionary.rules.displayName'),
            trigger: 'blur',
        },
    ],
    sort: [
        {
            required: true,
            type: 'number',
            message: i18n.global.t('upperComputer.dataDictionary.rules.sort'),
            trigger: 'blur',
        }
    ]
};

onMounted(() => {
    getTreeData();
    getForm();
});

async function getTreeData(): Promise<void> {
    treeData.value = await getDataDictionariesApi(props.code);
}

async function getForm(): Promise<void> {
    if (props.id) {
        form.value = await getDataDictionaryApi(props.id);
    }
}

function codeValidator(rule: Rule, value: string, callback: Function): Promise<void> {
    const reg: RegExp = /^[A-Z][a-zA-Z]{1,49}$/;
    if (reg.test(value)) {
        return Promise.resolve();
    }
    return Promise.reject(i18n.global.t('upperComputer.dataDictionary.rules.code'));
}

async function ok(): Promise<boolean> {
    try {
        await formRef.value?.validate();
        if (props.id) {
            await putDataDictionaryApi(form.value);
        } else {
            await postDataDictionaryApi(form.value);
        }
        message.success(i18n.global.t('common.' + (props.id ? 'editSuccess' : 'addSuccess')));
        return true;
    } catch {
        return false;
    }
}
</script>